home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1999 June: Reference Library / Dev.CD Jun 99 RL Disk 1.toast / Technical Documentation / Develop / develop Issue 28 / develop Issue 28 code / Sketch / Source / AppleEvent / OSASupport.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-08-11  |  7.4 KB  |  300 lines  |  [TEXT/CWIE]

  1. /****************************************************************************
  2.  * 
  3.  * OSASupport.c
  4.  * 
  5.  ****************************************************************************/
  6.  
  7. #include <stdio.h>
  8. #include <AppleScript.h>
  9. #include <Components.h>
  10.  
  11. #include "OSASupport.h"
  12. #include "Assertion.h"
  13. #include "StringUtils.h"
  14. #include "OSLHelpers.h"
  15.  
  16. static ComponentInstance fgScriptingComponentInstance;
  17. static ComponentInstance fgGenericScriptingComponent;
  18.  
  19. /*****************************************************************************
  20.  * 
  21.  * InitializeOSASupport
  22.  * 
  23.  *****************************************************************************/
  24.  
  25. Boolean InitializeOSASupport(void)
  26. {
  27.     OSErr error = noErr;
  28.     
  29.     if (fgScriptingComponentInstance == 0)
  30.         error = ConnectToScriptingComponent();
  31.  
  32.     return (error == noErr && fgScriptingComponentInstance != 0);
  33. }
  34.  
  35. /*****************************************************************************
  36.  * 
  37.  * HasOSASupport
  38.  * 
  39.  *****************************************************************************/
  40.  
  41. Boolean HasOSASupport(void)
  42. {
  43.     return (fgScriptingComponentInstance != 0);
  44. }
  45.  
  46. /*****************************************************************************
  47.  * 
  48.  * GetScriptingComponentInstance
  49.  * 
  50.  *****************************************************************************/
  51.  
  52. ComponentInstance
  53. GetScriptingComponentInstance(void)
  54. {
  55.     return fgScriptingComponentInstance;
  56. }
  57.  
  58. /*****************************************************************************
  59.  * 
  60.  * ConnectToScriptingComponent
  61.  * 
  62.  *****************************************************************************/
  63.  
  64. #define kMRGMinStackSize            65536L
  65. #define kMRGPreferredStackSize    65536L
  66. #define kMRGMaxStackSize            65536L
  67.  
  68. OSErr
  69. ConnectToScriptingComponent(void)
  70. {
  71.     OSErr                     error         = noErr;
  72.     OSErr                        ignoreError = noErr;
  73.     ComponentDescription description;
  74.     Component                component    = 0;
  75.  
  76.     Str255                     name;
  77.     AEDesc               componentName = {typeNull, nil};
  78.     
  79.     fgScriptingComponentInstance = 0;
  80.     
  81.     // What we're looking for:
  82.     // Defines are from OSA.h
  83.     
  84.     description.componentType                 = kOSAComponentType;
  85.     description.componentSubType             = kOSAGenericScriptingComponentSubtype;
  86.     description.componentManufacturer     = kAnyComponentManufacturer;
  87.     description.componentFlags             = kOSASupportsCompiling;
  88.     description.componentFlagsMask        = kOSASupportsCompiling;
  89.  
  90.     component = FindNextComponent((Component)0, &description);
  91.     
  92.     if (component == 0)
  93.     {
  94.         error = errOSACantOpenComponent;
  95.     }
  96.     else
  97.     {
  98.         ignoreError = GetComponentInfo(component, &description, nil, nil, nil);
  99.         fgScriptingComponentInstance = OpenComponent(component);
  100.         ignoreError = OSAScriptingComponentName(fgScriptingComponentInstance, &componentName);
  101.         DescToPString(&componentName, name, sizeof(name));
  102.     }
  103.     
  104.     if (fgScriptingComponentInstance == 0)
  105.         error = errOSACantOpenComponent;
  106. //    else
  107. //        error = ASInit(fgScriptingComponentInstance,         // Attempt to solve the stack overflow problem with Quark Converter script
  108. //                            kOSAModeNull,
  109. //                            kMRGMinStackSize,                            // commented out to remove write to NIL error
  110. //                            kMRGPreferredStackSize,
  111. //                            kMRGMaxStackSize,
  112. //                            kASDefaultMinHeapSize, 
  113. //                            kASDefaultPreferredHeapSize, 
  114. //                            kASDefaultMaxHeapSize);
  115.  
  116.     return error;
  117. }
  118.  
  119. /*****************************************************************************
  120.  * 
  121.  * LoadCompiledScript
  122.  * Load the script data from the file, and return its OSAID value
  123.  * 
  124.  *****************************************************************************/
  125.  
  126. OSAError
  127. LoadCompiledScript(FSSpec *fsSpec, OSAID *scriptID)
  128. {
  129.     short        fileRef         = 0;
  130.     OSAError    error          = noErr;
  131.     Handle    scriptHandle = nil;
  132.     AEDesc     scriptDesc     = {typeNull, nil};
  133.     
  134.     // Now open the Script the user selected
  135.     
  136.     fileRef = FSpOpenResFile(fsSpec,fsRdPerm);
  137.     error   = ResError();
  138.     
  139.     if (error == noErr)
  140.     {
  141.         scriptHandle = Get1Resource(kOSAScriptResourceType, 128);
  142.         
  143.         if (scriptHandle != nil)
  144.         {
  145.             scriptDesc.descriptorType = typeOSAGenericStorage;
  146.             scriptDesc.dataHandle     = scriptHandle;
  147.             
  148.             error = OSALoad(fgScriptingComponentInstance,
  149.                                  &scriptDesc,
  150.                                  kOSAModeNull,
  151.                                  scriptID);
  152.             ReleaseResource(scriptHandle);
  153.         }
  154.         CloseResFile(fileRef);
  155.         fileRef = 0;
  156.     }
  157.     return error;
  158. }
  159.  
  160. /*****************************************************************************
  161.  * 
  162.  * ExecuteScript
  163.  * 
  164.  *****************************************************************************/
  165.  
  166. OSAError
  167. ExecuteScript(OSAID scriptID)
  168. {
  169.     OSAError                 error         = noErr;
  170.     OSAError                    ignoreError = noErr;
  171.     OSAID                        resultID;
  172.            
  173.     short                startOffset;
  174.     short                endOffset;
  175.     
  176.     error = OSAExecute(fgScriptingComponentInstance,
  177.                              scriptID,
  178.                              kOSANullScript,
  179.                              kOSAModeNull,
  180.                              &resultID);
  181.                              
  182.     ignoreError = OSADispose(fgScriptingComponentInstance, scriptID);
  183.     ignoreError = OSADispose(fgScriptingComponentInstance, resultID);
  184.  
  185.     if (error == errOSAScriptError)
  186.     {
  187.         error = ExamineScriptError(fgScriptingComponentInstance, &startOffset, &endOffset);
  188.     }
  189.     
  190.     return error;
  191. }
  192.  
  193. //----------------------------------------------------------------------------------
  194.  
  195. OSErr
  196. ExamineScriptError(ComponentInstance componentInstance, short *startOffset, short *endOffset)
  197. {
  198.  
  199.     OSErr            error    = noErr;
  200.     
  201.     short            scriptError;
  202.     OSErr            ignoreError;
  203.     OSAError        theOSAError;
  204.  
  205.     AEDesc        errorDesc    = {typeNull, nil};
  206.     AEDesc        recordDesc    = {typeNull, nil};
  207.     DescType        actualType;
  208.     Size            actualSize;
  209.     
  210.     char        msg0[40];
  211.     char        msg1[256];
  212.     char        msg2[256];
  213.     
  214.     sprintf(msg0, "Script error");
  215.     sprintf(msg1, "No further information available");
  216.     msg2[0] = '\0';
  217.     
  218.     // Extract and cache the error number
  219.     
  220.     theOSAError = OSAScriptError(componentInstance,
  221.                                           kOSAErrorNumber,
  222.                                           typeShortInteger,
  223.                                           &errorDesc);
  224.     if (theOSAError == noErr)
  225.     {
  226.         scriptError = **(short**)(errorDesc.dataHandle);
  227.                     
  228.         sprintf(msg0, "Script error %d", scriptError);
  229.         
  230.         ignoreError = AEDisposeDesc(&errorDesc);
  231.         
  232.         if (scriptError == userCanceledErr)
  233.             return noErr;
  234.     }
  235.  
  236.     // Extract and cache the error message
  237.     
  238.     theOSAError = OSAScriptError(componentInstance,
  239.                                           kOSAErrorMessage,
  240.                                           typeChar,
  241.                                           &errorDesc);
  242.  
  243.     if (theOSAError == noErr)
  244.     {
  245.         TextToCString(errorDesc.dataHandle, msg1, sizeof(msg1));
  246.             
  247.         ignoreError = AEDisposeDesc(&errorDesc);
  248.     }
  249.     
  250.     // Extract and cache the source start and ending offsets
  251.      
  252.     theOSAError = OSAScriptError(componentInstance,
  253.                                           kOSAErrorRange,
  254.                                           typeOSAErrorRange,
  255.                                           &errorDesc);
  256.     if (theOSAError == noErr)
  257.     {
  258.         error = AECoerceDesc(&errorDesc, typeAERecord, &recordDesc);
  259.         
  260.         if (error == noErr)
  261.         {
  262.             ignoreError = AEDisposeDesc(&errorDesc);
  263.             
  264.             error = AEGetKeyPtr(&recordDesc,
  265.                                       keyOSASourceStart,
  266.                                       typeShortInteger,
  267.                                       &actualType,
  268.                                       startOffset,
  269.                                       sizeof(short),
  270.                                       &actualSize);
  271.                                                     
  272.             if (error == noErr)
  273.             {
  274.                 error = AEGetKeyPtr(&recordDesc,
  275.                                           keyOSASourceEnd,
  276.                                           typeShortInteger,
  277.                                           &actualType,
  278.                                           endOffset,
  279.                                           sizeof(short),
  280.                                           &actualSize);
  281.             
  282.                 if (!(*startOffset == 0 && *endOffset == 0))
  283.                     sprintf(msg2, "Source location: %d - %d", *startOffset, *endOffset);
  284.             }
  285.                                                      
  286.             ignoreError = AEDisposeDesc(&recordDesc);
  287.         }
  288.     }
  289.     
  290.     // Display the error message here!
  291.     
  292.     SysBeep(2);
  293.  
  294.     return noErr;
  295. }
  296.  
  297. //----------------------------------------------------------------------------------
  298.  
  299.  
  300.